#!/usr/bin/env python3
# -*- coding: utf-8 -*-

import sys
import time
import consul
from pathlib import Path

# 添加项目根目录到Python路径
sys.path.insert(0, str(Path(__file__).parent.parent))

from common.utils import LogUtil
from common.config import ServiceConfig
from dev_server.uitest_service import UiTestService
from dev_server.resource_service import ResourceService
from dev_server.webrtc_service import WebRTCService
from dev_server.device_context_mgr import DeviceContextMgr
from dev_server.zmq_server import ZmqServer

logger = LogUtil.get_logger(__name__)

class ServiceMgr:
    """设备服务器管理类"""
    
    def __init__(self, host: str, port: int, hdc_path: str = None):
        """初始化设备服务器

        Args:
            host (str): 设备服务器地址
            port (int): 资源服务器端口
            hdc_path (str): HDC文件路径
        """
        self.host = host
        self.port = port
        self.service_name = ServiceConfig.DEVICE_SERVICE_NAME
        self.service_id = self._generate_service_id()

        self.zmq_mgr = None
        self.device_context_mgr = None
        self.uitest_service = None
        self.webrtc_service = None
        self.resource_service = None
        self.consul_client = None
        
        try:
            self.zmq_mgr = ZmqServer(host)
            self.device_context_mgr = DeviceContextMgr(self.zmq_mgr, hdc_path=hdc_path)
            self.uitest_service = UiTestService(self.zmq_mgr, self.device_context_mgr)
            self.uitest_service.host = host
            self.uitest_service.port = port
            self.webrtc_service = WebRTCService(self.zmq_mgr, self.device_context_mgr)
            # 初始化Consul客户端
            self.resource_service = ResourceService(host, port)
            self.consul_client = consul.Consul(host=ServiceConfig.CONSUL_HOST, port=ServiceConfig.CONSUL_PORT)

        except Exception as e:
            logger.error(f"初始化设备服务器失败: {e}")
            self.destroy()
            raise e

    def destroy(self):
        """销毁设备服务器"""
        logger.info(f"销毁设备服务器: {self.service_id}")
        # 注销服务
        self._deregister_from_consul()
        if self.consul_client:
            self.consul_client = None
        # 停止服务
        if self.resource_service:
            self.resource_service.destroy()
            self.resource_service = None
        if self.uitest_service:
            self.uitest_service.destroy()
            self.uitest_service = None
        if self.webrtc_service:
            self.webrtc_service.destroy()
            self.webrtc_service = None
        # 销毁设备上下文管理器
        if self.device_context_mgr:
            self.device_context_mgr.destroy()
            self.device_context_mgr = None
        # 销毁ZMQ管理器
        if self.zmq_mgr:
            self.zmq_mgr.destroy()
            self.zmq_mgr = None

    def __del__(self):
        """析构函数"""
        self.destroy()

    def _generate_service_id(self) -> str:
        """生成唯一的服务ID"""
        import socket
        import uuid
        from datetime import datetime
        
        # 获取主机名
        hostname = socket.gethostname().replace('.', '-')
        
        # 获取时间戳
        timestamp = datetime.now().strftime('%Y%m%d%H%M%S')
        
        # 生成短UUID
        short_uuid = str(uuid.uuid4())[:8]
        
        return f"device-server-{hostname}-{timestamp}-{short_uuid}"

    def _register_to_consul(self):
        """向Consul注册服务"""
        if not self.consul_client:
            logger.warning("Consul客户端未初始化，跳过服务注册")
            raise ValueError("Consul客户端未初始化")
        
        # 注册服务
        rep_port = ServiceConfig.ZMQ_REP_PORT
        pub_port = ServiceConfig.ZMQ_PUB_PORT
        aio_port = ServiceConfig.ZMQ_AIO_PORT
        health_check_timeout = ServiceConfig.HEALTH_CHECK_TIMEOUT
        health_check_interval = ServiceConfig.HEALTH_CHECK_INTERVAL
        health_check_deregister = ServiceConfig.HEALTH_CHECK_DEREGISTER
        self.consul_client.agent.service.register(
            name=self.service_name,
            service_id=self.service_id,
            address=None,
            port=None,
            tags=[
                f'host={self.host}',
                f'rep_port={rep_port}',
                f'pub_port={pub_port}',
                f'res_port={self.port}',
                f'aio_port={aio_port}',
                f'timestamp={int(time.time())}',
            ],
            check=consul.Check.http(
                f"http://{self.host}:{self.port}/health",
                interval=health_check_interval,
                timeout=health_check_timeout,
                deregister=health_check_deregister
            )
        )
        
        logger.info(f"设备服务注册成功: {self.service_id}")
        logger.debug(f"设备服务地址：{self.host}")
        logger.debug(f"应答端口：{rep_port}")
        logger.debug(f"发布端口：{pub_port}")
        logger.debug(f"资源端口：{self.port}")
        logger.debug(f"异步端口：{aio_port}")
            
    def _deregister_from_consul(self):
        """从Consul注销服务"""
        if not self.consul_client:
            return
            
        try:
            self.consul_client.agent.service.deregister(self.service_id)
            logger.info(f"服务注销成功: {self.service_id}")
        except Exception as e:
            logger.error(f"服务注销失败: {e}")
            
    def start(self):
        """启动设备服务器"""
        logger.info("启动设备服务器...")
        try:
            # 启动设备上下文管理器
            self.device_context_mgr.start()
            logger.info("设备上下文管理器已启动")
            # 启动UiTest服务
            self.uitest_service.start()
            logger.info("UiTest服务已启动")
            # 启动WebRTC服务
            self.webrtc_service.start()
            logger.info("WebRTC服务已启动")
            # 启动资源服务
            self.resource_service.start()
            logger.info("资源服务已启动")
            # 注册到Consul
            self._register_to_consul()
            logger.info("设备服务器已注册到Consul")

            logger.info(f"设备服务器启动成功: {self.service_id}")
        except Exception as e:
            logger.error(f"启动设备服务器失败: {e}")
            self.destroy()

    def wait(self):
        """等待设备服务器停止"""
        while True:
            if self.device_context_mgr is None:
                logger.info("设备上下文管理器未初始化，设备服务器将退出")
                break
            if not self.device_context_mgr.is_alive():
                logger.info("设备上下文管理器已停止，设备服务器将退出")
                break
            if self.uitest_service is None:
                logger.info("UiTest服务未初始化，设备服务器将退出")
                break
            if not self.uitest_service.is_alive():
                logger.info("UiTest服务已停止，设备服务器将退出")
                break
            if self.resource_service is None:
                logger.info("资源服务未初始化，设备服务器将退出")
                break
            if not self.resource_service.is_alive():
                logger.info("资源服务已停止，设备服务器将退出")
                break
            if self.webrtc_service is None:
                logger.info("WebRTC服务未初始化，设备服务器将退出")
                break
            if not self.webrtc_service.is_alive():
                logger.info("WebRTC服务已停止，设备服务器将退出")
                break
            time.sleep(1)
        self.destroy()